package com.shadowlight.hero_story.asyncOperation;

import com.shadowlight.hero_story.MainThreadProcessor;
import lombok.extern.slf4j.Slf4j;

import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

/**
 * @Description todo
 * @Author cz
 * @Date 2022/3/17
 */
@Slf4j
public final class AsyncOperation {
    private static final AsyncOperation ASYNC_OPERATION = new AsyncOperation();
    private final ExecutorService[] es = new ExecutorService[Runtime.getRuntime().availableProcessors()];

    private AsyncOperation() {
        log.info("可用核数:{}", es.length);
        for (int i = 0; i < es.length; i++) {
            int finalI = i;
            es[i] = Executors.newSingleThreadExecutor(r -> {
                Thread thread = new Thread(r);
                thread.setName(String.format("AsyncOperationProcessor-%s", finalI));
                return thread;
            });
        }
    }


    public static AsyncOperation getInstance() {
        return ASYNC_OPERATION;
    }

    public void process(IAsyncOperation iAsyncOperation) {
        if (iAsyncOperation == null) {
            return;
        }

        int bindId = Math.abs(iAsyncOperation.getBindId());
        int idx = bindId % es.length;
        es[idx].submit(() -> {
            try {
                iAsyncOperation.doAsync(); //异步

                MainThreadProcessor.getInstance().process(iAsyncOperation::doFinish);   //主线程同步操作
            } catch (Exception e) {
                log.error("异步线程执行出错！");
            }

        });
    }

}
